﻿using UnityEngine;
using UnityEngine.Events;
using UnityEngine.EventSystems;

public class MouseOnOrOver : MonoBehaviour, IPointerEnterHandler, IPointerExitHandler, IPointerDownHandler, IPointerUpHandler
{
    public UnityEvent onEnter = new UnityEvent();
    public UnityEvent<PointerEventData> onEnterWithData = new UnityEvent<PointerEventData>();
    
    public UnityEvent onExit = new UnityEvent();
    public UnityEvent<PointerEventData> onExitWithData = new UnityEvent<PointerEventData>();

    public UnityEvent onLeftMouseEnter = new UnityEvent();
    public UnityEvent<PointerEventData> onLeftMouseEnterWithData = new UnityEvent<PointerEventData>();

    public UnityEvent onRightMouseEnter = new UnityEvent();
    public UnityEvent<PointerEventData> onRightMouseEnterWithData = new UnityEvent<PointerEventData>();

    private UnityAction toggleAction;

    private bool _isMouseOn;
    private PointerEventData.InputButton _currentPressedButton = PointerEventData.InputButton.Left;

    public bool isMouseOn
    {
        get => _isMouseOn;
        set => _isMouseOn = value;
    }

    public bool isMouseOver
    {
        get => isMouseOn;
        set => isMouseOn = value;
    }

    public void AddOn(UnityAction action) => onEnter.AddListener(action);
    public void AddOn(UnityAction<PointerEventData> action) => onEnterWithData.AddListener(action);

    public void AddOff(UnityAction action) => onExit.AddListener(action);
    public void AddOff(UnityAction<PointerEventData> action) => onExitWithData.AddListener(action);

    public void AddLeftOn(UnityAction action) => onLeftMouseEnter.AddListener(action);
    public void AddLeftOn(UnityAction<PointerEventData> action) => onLeftMouseEnterWithData.AddListener(action);

    public void AddRightOn(UnityAction action) => onRightMouseEnter.AddListener(action);
    public void AddRightOn(UnityAction<PointerEventData> action) => onRightMouseEnterWithData.AddListener(action);

    public void AddToggle(UnityAction _)
    {
        toggleAction += _;
    }

    public void OnPointerEnter(PointerEventData eventData)
    {
        isMouseOn = true;

        onEnter.Invoke();
        onEnterWithData.Invoke(eventData);

        if (_currentPressedButton == PointerEventData.InputButton.Left)
        {
            onLeftMouseEnter.Invoke();
            onLeftMouseEnterWithData.Invoke(eventData);
        }
        else if (_currentPressedButton == PointerEventData.InputButton.Right)
        {
            onRightMouseEnter.Invoke();
            onRightMouseEnterWithData.Invoke(eventData);
        }

        toggleAction?.Invoke();
    }

    public void OnPointerExit(PointerEventData eventData)
    {
        isMouseOn = false;

        onExit.Invoke();
        onExitWithData.Invoke(eventData);

        toggleAction?.Invoke();
    }

    public void OnPointerDown(PointerEventData eventData)
    {
        _currentPressedButton = eventData.button;
    }

    public void OnPointerUp(PointerEventData eventData)
    {
        _currentPressedButton = PointerEventData.InputButton.Left;
    }
}